package com.lazyframework.security.admin.authentication;

import com.lazyframework.commons.support.ResponseModels;
import com.lazyframework.security.admin.properties.JwtProperties;
import io.jsonwebtoken.Jwts;
import io.jsonwebtoken.SignatureAlgorithm;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.web.authentication.AuthenticationSuccessHandler;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.Base64;
import java.util.Date;

/**
 * Create by lazy in 2019/9/28
 */
public class RestfullAuthenticationSuccessHandler implements AuthenticationSuccessHandler {

    private JwtProperties jwtProperties;

    private LoginLogService loginLogService;

    public RestfullAuthenticationSuccessHandler() {}

    public RestfullAuthenticationSuccessHandler(JwtProperties props) {
        this.jwtProperties = props;
    }

    @Override
    public void onAuthenticationSuccess(HttpServletRequest request, HttpServletResponse response,
                                        Authentication authentication) throws IOException {
        // Get user from security context
        UserDetails userDetails = (UserDetails) authentication.getPrincipal();

        // Save login log
        loginLogService.save(request, response, authentication);

        // Generate JWT
        String jwt = Jwts.builder()
                .setIssuer(jwtProperties.getIssuer())
                .setIssuedAt(new Date())
                .claim("username", userDetails.getUsername())
                .setExpiration(new Date(System.currentTimeMillis() + (jwtProperties.getExpire() * 1000)))
                .signWith(SignatureAlgorithm.HS256, Base64.getEncoder().encodeToString(jwtProperties.getSecretKey().getBytes()))
                .compact();

        // Write with JSON
        ResponseModels.ok(response, jwt);
    }

    public void setJwtProperties(JwtProperties props) {
        this.jwtProperties = props;
    }

    public void setLoginLogService(LoginLogService loginLogService) {
        this.loginLogService = loginLogService;
    }
}
